﻿
/*******************************************************************
 * Module：ObjectContainer.cs
 * Author：LYH
 * Created：2012-06-07 09:42:09Z
 * Description：Spring容器封装类
 * *******************************************************************/

using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.Diagnostics;
using System.Linq;
using System.Reflection;
using System.Text;
using Spring.Context;
using Spring.Context.Support;

namespace ModularAndPlugin.Core
{
    /// <summary>
    /// Spring容器封装类
    /// </summary>
    public class ObjectContainer
    {
        //private static log4net.ILog log = log4net.LogManager.GetLogger("ObjectContainer");
        /// <summary>
        /// 获取应用程序上下文.
        /// </summary>
        /// <returns><see cref="IApplicationContext"/>应用程序上下文.</returns>
        public static IApplicationContext GetContext()
        {
            try
            {
                if (FApplicationContext == null)
                {
                    FApplicationContext = ContextRegistry.GetContext();
                }
                return FApplicationContext;
            }
            catch (Exception ex)
            {
                //log.Error("出现异常", ex);

            }
            return null;
        }
        /// <summary>
        /// 重置应用程序上下文.
        /// </summary>
        /// <returns><see cref="IApplicationContext"/>应用程序上下文.</returns>
        public static void ResetContext()
        {
            try
            {
                ContextRegistry.Clear();
                FApplicationContext = ContextRegistry.GetContext();
            }
            catch (Exception ex)
            {
                //log.Error("出现异常", ex);

            }
            return;
        }
        /// <summary>
        /// 获取应用程序上下文.
        /// </summary>
        /// <param name="name"><see cref="IApplicationContext"/>应用程序上下文名称.</param>
        /// <returns><see cref="IApplicationContext"/>应用程序上下文.</returns>
        public static IApplicationContext GetContext(string name)
        {
            return ContextRegistry.GetContext(name);
        }

        /// <summary>
        /// 获取对象.
        /// </summary>
        /// <typeparam name="T">对象的类型.</typeparam>
        /// <param name="id">标识.</param>
        /// <returns></returns>
        public static T GetObject<T>(string id)
        {
            //SetCetificate();
            IApplicationContext IApp = GetContext();

            return (T)IApp.GetObject(id);
        }



        /// <summary>
        /// 获取对象类表.
        /// </summary>
        /// <typeparam name="T">对象的类型.</typeparam>
        /// <returns></returns>
        public static IList<T> GetObjects<T>()
        {
            IEnumerable items = GetContext().GetObjectsOfType(typeof(T));
            IList<T> objects = new List<T>();
            foreach (DictionaryEntry item in items)
            {
                objects.Add((T)item.Value);
            }
            return objects;
        }
        /// <summary>
        /// 获取对象类.
        /// </summary>
        /// <typeparam name="tp">对象的契约类型.</typeparam>
        /// <returns></returns>
        public static object GetObject(string tpName)
        {
            if (IsHas(tpName))
            {
                return GetContext().GetObject(tpName);
            }
            else
            {
                return null;
            }
        }

        public static bool IsHas(string tpName)
        {
            IList<string> Names = GetContext().GetObjectDefinitionNames();
            if (Names == null || Names.Count <= 0) return false;
            return Names.Contains(tpName);
        }
        /// <summary>
        /// 根据Import特性赋值
        /// </summary>
        /// <param name="obj">源对象</param>
        public static void Compose(object obj)
        {
            try
            {
                var importFilds = obj.GetType().GetFields().Where(
        itm => itm.GetCustomAttributes(typeof(ImportAttribute), true).Any());
                foreach (FieldInfo fieldInfo in importFilds)
                {
                    fieldInfo.SetValue(obj, GetObject(fieldInfo.FieldType.Name));
                }
                var importProp = obj.GetType().GetProperties().Where(
                    itm => itm.GetCustomAttributes(typeof(ImportAttribute), true).Any());
                foreach (PropertyInfo Info in importProp)
                {
                    Info.SetValue(obj, GetObject(Info.PropertyType.Name), null);
                }
            }
            catch (Exception ex)
            {
                
                //throw;
            }
        }
        [ThreadStatic]
        private static IApplicationContext FApplicationContext;

    }
}
